package com.ccjk.beusoft.thirdlib.plugin1.hook.handler;

import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.ApplicationInfo;
import android.os.Handler;
import android.os.Message;

import com.ccjk.beusoft.thirdlib.plugin1.PluginManager1;

import java.lang.reflect.Field;

import static com.ccjk.beusoft.thirdlib.plugin1.hook.Hook.KEY_REAL_ACTIVITY;

/**
 * Created by CCJK on 2017/12/20.
 * ActivityThread 中 H的Callbakc
 */

public class HCallbackProxy implements Handler.Callback {
    private Handler mH;
    private Context context;

    public HCallbackProxy(Handler mH, Context context) {
        this.mH = mH;
        this.context = context;
    }


    @Override
    public boolean handleMessage(Message msg) {
        switch (msg.what) {
            // ActivityThread里面 "LAUNCH_ACTIVITY" 这个字段的值是100
            // 本来使用反射的方式获取最好, 这里为了简便直接使用硬编码
            case 100:
                handleLaunchActivity(msg);
                return false;
        }
        mH.handleMessage(msg);
        return true;
    }

    /**
     * 将ActivityManagerHook里面替换掉的Activity回复为真实的TargetActivity
     *
     * @param msg
     */
    private void handleLaunchActivity(Message msg) {
        try {
            //实际类型为ActivityClientRecord
            Object activityClientRecord = msg.obj;

            Class clazz = activityClientRecord.getClass();
            Field intentField = clazz.getDeclaredField("intent");
            intentField.setAccessible(true);
            //这个是我们需要的
            Intent intent = (Intent) intentField.get(activityClientRecord);
            Intent realIntent = intent.getParcelableExtra(KEY_REAL_ACTIVITY);
            if (realIntent != null) {
                intent.setComponent(realIntent.getComponent());
            }
            //activityClientRecord 的activityinfo 里面的ApplicationInfo还是宿主的applicationInfo
            //需要替换成插件的
            Object loadedApk= PluginManager1.get().getLoadedApk(realIntent.getComponent().getPackageName());
            Field applicatonField=loadedApk.getClass().getDeclaredField("mApplicationInfo");
            applicatonField.setAccessible(true);
            ApplicationInfo pluginApplicationInfo= (ApplicationInfo) applicatonField.get(loadedApk);

            Field field=clazz.getDeclaredField("activityInfo");
            field.setAccessible(true);
            ActivityInfo activityInfo= (ActivityInfo) field.get(activityClientRecord);
            activityInfo.applicationInfo=pluginApplicationInfo;

            //
//            Field packageInfoField = clazz.getDeclaredField("packageInfo");
//            packageInfoField.setAccessible(true);
//            packageInfoField.set(activityClientRecord, PluginManager1.get().getLoadedApk(realIntent.getComponent().getPackageName()));
//
//
//            Class activityThreadClass = Class.forName("android.app.ActivityThread");
//            Method currentActivityThreadMethod = activityThreadClass.getDeclaredMethod("currentActivityThread");
//            currentActivityThreadMethod.setAccessible(true);
//            Object activityThread = currentActivityThreadMethod.invoke(null);
//
//            Method handleLaunchActivityMethod=activityThreadClass.getDeclaredMethod("handleLaunchActivity",
//                    new Class[]{clazz,Intent.class});
//            handleLaunchActivityMethod.setAccessible(true);
//            handleLaunchActivityMethod.invoke(activityThread,activityClientRecord,null);
        } catch (Exception e) {
            e.printStackTrace();
        }


    }
}
